#include "wren_function_extension.hpp"
#include "scripting/scripting_module.h"
#include "wren_base.hpp"
#include "fmt/core.h"
#include <wrenbind17/wrenbind17.hpp>


WrenFunctionExtension::WrenFunctionExtension(std::string title, const std::string &script_path):
    IFunctionalScript(std::move(title), script_path, g_current_module),
    WrenScriptBase(script_path, "Functional")
{
}

WrenFunctionExtension::~WrenFunctionExtension()
{
}

void WrenFunctionExtension::execute()
{
    try {
        auto &vm = WrenShared::SharedVM();
        auto var = vm.find(module_name, "main");
        auto call = var.func("call()");
        if (call)
        {
            call();
        }
    }
    catch (std::exception &e)
    {
        fprintf(stderr, "Wren run error: %s\n", e.what());
    }
}

IScript* WrenFunctionExtension::create(std::string title, std::string_view code, const std::string &script_path)
{
    WrenFunctionExtension *ext = new WrenFunctionExtension(std::move(title), script_path);
    if (!ext->compile(code))
    {
        delete ext;
        ext = nullptr;
    }
    return ext;
}

bool WrenFunctionExtension::compile(const std::string_view& code) const
{
    try 
    {
        auto &vm = WrenShared::SharedVM();
        auto& m = vm.module(module_name);
        m.append(std::string{ code });
        vm.runFromSource("main", fmt::format("import \"{}\"", module_name));
    }
    catch (std::exception &e)
    {
        fprintf(stderr, "Wren compile error: %s\n", e.what());
        return false;
    }
    return true;
}
